﻿//////////////////////////////////////////////////////////////////////////////
//
// Copyright © 1998-2024 Glodon Company Limited.
//
// Licensed under the MIT License
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the “Software”),
// to deal in the Software without restriction, including without limitation
// the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
// sell copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
//
//////////////////////////////////////////////////////////////////////////////
#include "RecentDocumentPathRecord.h"
#include "GbmpFileSystem.h"
#include "QtXml/qdom.h"
#include "QTextStream"
#include "QFile"
#include "IPublishConfig.h"
#include "EnableCompileWarning_The_LAST_IncludeInCpp.h"


using namespace gcmp;

#define RootQString      "WelcomneDlg"
#define NoodQString      "Documnet"
#define AttributeQString "Path"


RecentDocumentPathRecord::RecentDocumentPathRecord()
{
    m_RecordCountMax = 10;
    m_DocumentFileSuffixesFilter = QString::fromStdWString(L"");
    m_RecordFilePath = FileSystem::GetExeDirPath() + L"RecentDocumentPathRecord.xml";
    // 如果是对外发布的版本, templates在appdata\GMJ3.0中获取
    const IConfigRecord* pInHouseModeConfigRecord = IPublishConfig::GetConfigRecord(PublishConfigRecordNames::InHouseMode);
    if (pInHouseModeConfigRecord && !pInHouseModeConfigRecord->IsInternalIdentifyCodeValue())
    {
        m_RecordFilePath = gcmp::FileSystem::GetLocalAppDataDirPath(L"GMJ3.0") + L"RecentDocumentPathRecord.xml";
    }
}

RecentDocumentPathRecord::~RecentDocumentPathRecord(void)
{
    FlushRecord();
}

RecentDocumentPathRecord* RecentDocumentPathRecord::Get()
{
    static RecentDocumentPathRecord mng;
    return &mng;
}


void RecentDocumentPathRecord::SetRecordFilePath(const std::wstring& val) 
{
    m_RecordFilePath = val; 
    InitFromRecordFile();
}
void RecentDocumentPathRecord::SetDocumentFileSuffixesFilter(const QString& val)
{ 
    m_DocumentFileSuffixesFilter = val.toLower();
    InitFromRecordFile();
}


int RecentDocumentPathRecord::GetRecordCont()
{
    return (int)m_documentPaths.size();
}

QString RecentDocumentPathRecord::GetRecordPath(int index)
{
    return m_documentPaths.at(index);
}

void RecentDocumentPathRecord::AddDocumentPath(const QString& path)
{
    int first = path.lastIndexOf("."); //从后面查找"/"位置
    QString fileSuffixes = path.right(path.length() - first - 1); //从右边截取
    if(!m_DocumentFileSuffixesFilter.isEmpty()
        &&!m_DocumentFileSuffixesFilter.contains(fileSuffixes.toLower()))
        return;

    bool isHave = false;
    QString value = path;
    value = value.replace(QString::fromStdWString(L"\\"), QString::fromStdWString(L"/"));

    for (int i = 0; i < (int)m_documentPaths.size(); i++)
    {
        if (m_documentPaths.at(i) == value)
        {
            isHave = true;
            m_documentPaths.erase(m_documentPaths.begin() + i);
            m_documentPaths.push_back(value);
        }
    }
    if (!isHave)
    {
        m_documentPaths.push_back(value);
        if (m_documentPaths.size() > m_RecordCountMax)
            m_documentPaths.erase(m_documentPaths.begin() + (int)m_documentPaths.size() - 1);
    }
    FlushRecord();
}

void RecentDocumentPathRecord::InitFromRecordFile()
{
    //打开或创建文件
    m_documentPaths.clear();
    QFile file(QString::fromStdWString(m_RecordFilePath)); //相对路径、绝对路径、资源路径都可以
    if (!file.open(QFile::ReadOnly))
    {
        FlushRecord();
        return;
    }
    QDomDocument doc;
    if (!doc.setContent(&file))
    {
        file.close();
        return;
    }
    file.close();

    QDomElement root = doc.documentElement(); //返回根节点
    if(RootQString!=root.nodeName())
        return ;
    QDomNode node = root.firstChild(); //获得第一个子节点
    while (!node.isNull())  //如果节点不空
    {
        if (node.isElement()) //如果节点是元素
        {
            QDomElement e = node.toElement(); //转换为元素，注意元素和节点是两个数据结构，其实差不多
            if(NoodQString!=e.tagName())
                continue;
            QString value = e.attribute(AttributeQString);
            //检查文件是否存在
            QFile checkFile(value);
            if (!checkFile.exists())
            {
                node = node.nextSibling();
                continue;
            }
            AddDocumentPath(value);
        }
        node = node.nextSibling(); //下一个兄弟节点,nextSiblingElement()是下一个兄弟元素，都差不多
    }

}

void RecentDocumentPathRecord::FlushRecord()
{
    QFile file(QString::fromStdWString(m_RecordFilePath)); //相对路径、绝对路径、资源路径都可以
    if (!file.open(QFile::WriteOnly | QFile::Truncate)) //可以用QIODevice，Truncate表示清空原来的内容
        return;

    QDomDocument doc;
    //写入xml头部
    QDomProcessingInstruction instruction; //添加处理命令
    instruction = doc.createProcessingInstruction("xml", "version=\"1.0\" encoding=\"UTF-8\"");
    doc.appendChild(instruction);
    QDomElement root = doc.createElement(RootQString);
    //添加根节点
    for (int i = 0; i < (int)m_documentPaths.size(); i++)
    {
        //if (!QFile.exists(QString::fromStdString(m_documentPaths.at(i))))
        //    continue;
        doc.appendChild(root);
        //添加第一个子节点及其子元素
        QDomElement nood = doc.createElement(NoodQString);
        nood.setAttribute(AttributeQString, m_documentPaths.at(i)); //方式一：创建属性  其中键值对的值可以是各种类型
        root.appendChild(nood);
    }
    //输出到文件
    QTextStream out_stream(&file);
    doc.save(out_stream, 4); //缩进4格
    file.close();
}

